import { createRouter, createWebHistory } from 'vue-router'

import Login from '@/views/login/LoginView.vue'
import YwuRouteIndex from '@/views/routeIndex/YwuRouteIndex.vue'
import YwuLayout from '@/views/ywuLayout/YwuLayout.vue'

import {queryMenuRegisterInfo} from "@/request/menu";
import {registerComponent} from "@/utils/ywuCommon";

import {app} from '@/main'
import {useAppStore} from "@/stores/app";

const router = createRouter({
  history: createWebHistory(import.meta.env.BASE_URL),
  routes: [
    {
      path: '/',
      component: YwuRouteIndex,
      name: 'ywu-route-index'
    },
    {
      path: '/super-ywu',
      component: YwuLayout,
      name: 'ywu-home',
      redirect: '/super-ywu/index',
      children: []
    },
    {
      path: '/login',
      name: 'login',
      component: Login
    },
    {
      path: '/404',
      name: '404',
      component: () => import('@/views/error/400.vue')
    },
    {
      path: '/403',
      name: '403',
      component: () => import('@/views/error/403.vue')
    },
    {
      path: '/400',
      name: '400',
      component: () => import('@/views/error/400.vue')
    },
    {
      path: '/500',
      name: '500',
      component: () => import('@/views/error/500.vue')
    }
  ],
})

// 1. 定义所有可能用到的组件（使用懒加载）
const components = {
  ywuIndex: () => import('@/views/index/Index.vue'),
  menuManageIndex: () => import('@/views/menuManage/index.vue'),
  apiManageIndex: () => import('@/views/apiManage/index.vue'),
  userRoleManageIndex: () => import('@/views/userRoleManage/index.vue'),
  apiRouterManageIndex: () => import('@/views/apiManage/apiRouterManage/index.vue'),
  apiCacheManageIndex: () => import('@/views/apiManage/apiCacheManage/index.vue'),
  userRoleManageUserIndex: () => import('@/views/userRoleManage/user/index.vue'),
  userRoleManageRoleIndex: () => import('@/views/userRoleManage/role/index.vue'),
  serviceManageIndex: () => import('@/views/serviceManage/index.vue'),
  serviceRegisterManageIndex: () => import('@/views/serviceManage/serviceRegisterManage/index.vue'),
  serviceInstanceManageIndex: () => import('@/views/serviceManage/serviceInstanceManage/index.vue'),
  serviceConfigManageIndex: () => import('@/views/serviceManage/serviceConfigManage/index.vue'),
  containerManageIndex: () => import('@/views/containerManage/index.vue'),
  containerManageManageIndex: () => import('@/views/containerManage/containerManage/index.vue'),
  containerLogManageIndex: () => import('@/views/containerManage/containerLogManage/index.vue'),
  lowcodeIndex: () => import('@/views/lowcode/index.vue'),
  componentManageIndex: () => import('@/views/lowcode/componentManage/index.vue'),
  lowcodeBuilderIndex: () => import('@/views/lowcode/lowCodeBuilder/index.vue'),
  menuManageManageIndex: () => import('@/views/menuManage/menuManage/index.vue'),
  routeRootPathIndex: () => import('@/views/menuManage/routeRootPath/index.vue'),
  containerPipelineManageIndex: () => import('@/views/containerManage/containerPipelineManage/index.vue'),
  userRoleManageTenantIndex: () => import('@/views/userRoleManage/tenant/index.vue'),
  containerInstanceDetailIndex: () => import('@/views/containerManage/containerInstanceDetail/index.vue'),
  userRoleManageTenantAuthIndex: () => import('@/views/userRoleManage/tenantAuth/index.vue'),
  apiServiceManageIndex: () => import('@/views/apiService/index.vue'),
  buildForm: () => import('@/views/bpmn/form/BuildForm.vue'),
  FormInstanceList: () => import('@/views/bpmn/form/FormInstanceList.vue'),
  FormInterfaceList: () => import('@/views/bpmn/form/FormInterfaceList.vue'),
  BuildFlow: () => import('@/views/bpmn/flow/BuildFlow.vue'),
  BuildFlowForm: () => import('@/views/bpmn/flow/BuildFlowForm.vue'),
  MyToDoInstanceList: () => import('@/views/bpmn/todo/MyToDoInstanceList.vue'),
  CompleteHistoryList: () => import('@/views/bpmn/todo/CompleteHistoryList.vue'),
  CompleteFlowInstance: () => import('@/views/bpmn/todo/CompleteFlowInstance.vue'),
  HistoryFlowInstance: () => import('@/views/bpmn/todo/HistoryFlowInstance.vue'),
  StartFlowInstance: () => import('@/views/bpmn/todo/StartFlowInstance.vue'),
  FlowFormInstanceList: () => import('@/views/bpmn/flow/FlowFormInstanceList.vue'),
}


async function doRouterBeforeEach(to, from, next) {
  useAppStore().resetMainContainerLoading(true);
  if (!judgeRouteIsExist(to.path)) {
    // 查询菜单、文根、组件等相关信息
    let requestParam = {
      routeTo: to.fullPath
    }
    let registerInfo;
    try {
      registerInfo = await queryMenuRegisterInfo(requestParam);
    } catch (e) {
      await router.replace({path: "/404"})
      return
    }
    // 组件信息
    let componentInfoList = registerInfo.data["componentInfo"];
    // 文根信息
    let routeRootPathList = registerInfo.data["routeRootPath"];
    // 菜单信息
    let menuInfo = registerInfo.data["menuInfo"];
    // 如果查询出的菜单结果信息为空，则进行404
    if (!menuInfo || !menuInfo.id) {
      await router.push({path: "/404"})
    }
    // 注入所有的组件
    for (let i = 0; i < componentInfoList.length; i++) {
      let componentInfo = componentInfoList[i];
      registerComponent(componentInfo);
    }
    // 路由文根关联路由组件并注入到VUE-ROUTER中
    for (let i = 0; i < routeRootPathList.length; i++) {
      let data = routeRootPathList[i]
      if (data.routeRootPath === '/ywu') {
        continue;
      }
      // 路由文根不存在，创建路由文根路由对象
      if (!judgeRouteIsExist(data.routeRootPath)) {
        let componentFilterList = componentInfoList.filter(res => res.id === data.componentId)
        if (componentFilterList.length === 0) {
          continue;
        }
        let componentFilter = componentFilterList[0]
        let routeInfo = {
          path: data.routeRootPath,
          name: data.routeRootName,
          component: app.component(componentFilter.componentName)
        }
        router.addRoute(routeInfo);
      }
    }
    // 根据查询出的数据构建VUE-ROUTER
    handlerRoute(menuInfo, "", componentInfoList, false, routeRootPathList)
    // 再次判断路由是否存在
    if (!judgeRouteIsExist(to.path)) {
      await router.replace({path: "/404"})
    } else {
      next(to);
    }
  } else {
    next()
  }
  setTimeout(() => {
    useAppStore().resetMainContainerLoading(false);
  }, 500);
}

// 前置路由守卫  -  获取后端存储的动态路由
router.beforeEach((to, from, next) => {
  doRouterBeforeEach(to, from, next).then(r => {})
})

// 递归创建路由 -- 子路由
function handlerRoute(data, parentName, componentRes, isChild, routeRootPathList) {
  // 判断路由是否存在
  if (judgeRouteIsExist(data.routeTo)) {
    // 判断当前路由是否存在，存在则递归进行子路由的创建
    if (data.children !== null && data.children.length > 0) {
      handlerRoute(data.children[0], data.name, componentRes, true, routeRootPathList);
    }
    return;
  }
  // 添加当前路由
  let resDataInfo = {}
  // 判断当前菜单类型是否为动态组件
  if (data["menuType"] === 'DYNAMIC') {
    // 动态组件
    // 根据componentId关联组件
    let componentInfoList = componentRes.filter(res => res.id === data["componentId"]);
    if (componentInfoList && componentInfoList.length > 0) {
      let componentInfo = componentInfoList[0];
      // 构建路由组件
      let newMeta = data.meta.replaceAll("\'", "\"")
      resDataInfo = {
        path: `${data.routePath}`,
        component: app.component(componentInfo["componentName"]),
        name: `${data.name}`,
        meta: JSON.parse(newMeta)
      };
    }
  } else {
    // 静态菜单
    let newMeta = data.meta.replaceAll("\'", "\"")
    resDataInfo = {
      path: `${data["routePath"]}`,
      component: components[data.componentPath],
      name: `${data.name}`,
      meta: JSON.parse(newMeta)
    };
  }
  if (parentName === "") {
    let routeRootFilterList = routeRootPathList.filter(res => res.id === data.routeRootId);
    if (routeRootFilterList.length === 0) {
      console.log("route root path error")
      return
    }
    let routeRootFilter = routeRootFilterList[0]
    parentName = routeRootFilter.routeRootName;
  }
  router.addRoute(parentName, resDataInfo);
  // 判断当前路由是否存在，存在则递归进行子路由的创建
  if (data.children && data.children.length > 0) {
    handlerRoute(data.children[0], data.name, componentRes, true, routeRootPathList);
  }
}

// 判断当前执行的路由是否存在
function judgeRouteIsExist(path) {
  const routesInfo = router.getRoutes();
  const tempList = routesInfo.filter(res => res.path === path);
  return tempList.length > 0;
}

export default router
